import React, { useEffect, useState } from 'react';
import { Modal, Layout } from 'antd';
import { listen } from '@tauri-apps/api/event';
import { useMemoizedFn, useRequest } from 'ahooks';
import { TabPaneTypeEnum } from '@/utils/enums';
import List from './components/List';
import {
  delTabPaneByCode,
  insertTabPane,
  queryTabPanes,
  updateTabPaneByCode,
  clearTabPanes,
} from '@/services';
import { stopProject, stopAllProcess } from '@/services/command';

import TabsContent from './components/TabsContent';

import './index.less';
import useCreateImportWindow from './hooks/useCreateImportWindow';

let unlistenClose: any;
let unlistenCreateWindow: any;

const { Sider, Content } = Layout;

function turnProjectToTabPane(project: ProjectItem): TabPaneData {
  const { name, code } = project;
  return {
    title: name as string,
    closeable: true,
    code,
    type: TabPaneTypeEnum.WORKER,
    data: project,
  };
}

interface TabsPageProps {}
// tab中项目编码和序号对应的映射
const tabsPageCodeIndexMap = new Map();

const TabsPage: React.FC<TabsPageProps> = () => {
  const [tabList, setTabList] = useState<TabPaneData[]>([]);

  const [activeKey, setActiveKey] = useState<string | undefined>();

  const { run: getTabPanesRun } = useRequest(queryTabPanes, {
    manual: true,
    onSuccess(ret: any) {
      const ntabList = Array.from(Array.isArray(ret) ? ret : []);
      console.log(50, ntabList);
      if (tabList.length === 0 && ntabList.length > 0) {
        setActiveKey(ntabList[0].code);
      }
      setTabList(ntabList);
      flushTabsPageCodeIndexMap(ntabList);
    },
  });

  const { run: clearTabPanesRun } = useRequest(clearTabPanes, {
    manual: true,
    onSuccess(ret: any) {
      setTabList([]);
      flushTabsPageCodeIndexMap([]);
    },
  });

  const { runAsync: saveRun } = useRequest(insertTabPane, {
    manual: true,
  });

  const { run: updateRun } = useRequest(updateTabPaneByCode, {
    manual: true,
  });

  const { runAsync: delRun } = useRequest(delTabPaneByCode, {
    manual: true,
  });

  useEffect(() => {
    getTabPanesRun();
  }, []);

  // 开启项目
  const onProjectStart = useMemoizedFn((project: ProjectItem) => {
    const tabPane = turnProjectToTabPane(project);
    if (tabsPageCodeIndexMap.has(tabPane.code)) {
      setActiveKey(tabPane.code as string);
      return;
    }
    saveRun(tabPane).then(() => {
      const nTabList = [...tabList, tabPane];
      setTabList(nTabList);
      setActiveKey(tabPane.code as string);
      flushTabsPageCodeIndexMap(nTabList);
    });
  });
  // 修改项目
  const onProjectChange = useMemoizedFn((project: ProjectItem) => {
    const { code, commands } = project;
    const tabIndex = tabsPageCodeIndexMap.get(code);
    if (tabIndex >= 0) {
      const tabPane = turnProjectToTabPane(project);
      const tabData = tabList[tabIndex];
      const { commandTerminals } = tabData.data || {};
      const cmdMap = new Map();
      commands?.forEach((cmd) => {
        cmdMap.set(cmd.key as string, cmd.command);
      });
      commandTerminals?.forEach((terminal) => {
        if (
          cmdMap.has(terminal.key) &&
          cmdMap.get(terminal.key) !== terminal.command
        ) {
          terminal.command = cmdMap.get(terminal.key);
        }
      });
      (tabPane.data as any).commandTerminals = commandTerminals;
      updateRun(tabPane);
      getTabPanesRun();
    }
  });
  // 更新终端信息
  const changeWorkData = useMemoizedFn(
    (code: string, workerData: WorkerData) => {
      const tabIndex = tabsPageCodeIndexMap.get(code);
      if (tabIndex >= 0) {
        const tabData = tabList[tabIndex];
        tabData.data = workerData;
        updateRun(tabData);
      }
    },
  );

  const { createImportWindow } = useCreateImportWindow();

  const initListen = async () => {
    unlistenClose = await listen<string>('close', () => stopAllProcess());
    unlistenCreateWindow = await listen<string>('createWindow', (params) => {
      if (params.payload === 'IMPORT') createImportWindow();
    });
  };

  useEffect(() => {
    initListen();
    return () => {
      unlistenClose && unlistenClose();
      unlistenCreateWindow && unlistenCreateWindow();
    };
  }, []);

  const delTabPane = useMemoizedFn((code: any) => {
    Modal.confirm({
      title: '删除',
      content: '是否关闭该项目？',
      centered: true,
      onOk: () =>
        new Promise((resolve, reject) => {
          delRun(code)
            .then(() => {
              const index = tabsPageCodeIndexMap.get(code);
              tabList.splice(index, 1);
              if (code === activeKey) {
                if (tabList.length > 0) {
                  const nextIndex = Math.min(index, tabList.length - 1);
                  const nextCode = tabList[nextIndex].code;
                  setActiveKey(nextCode as string);
                } else {
                  setActiveKey(undefined);
                }
              }
              flushTabsPageCodeIndexMap(tabList);
              stopProject(code);
              setTabList([...tabList]);
              resolve(1);
            })
            .catch(reject);
        }),
    });
  });

  const flushTabsPageCodeIndexMap = (tabList: TabPaneData[]) => {
    tabsPageCodeIndexMap.clear();
    tabList.forEach((tab, index) => {
      tabsPageCodeIndexMap.set(tab.code, index);
    });
  };

  return (
    <Layout className="tabs-page">
      <Sider>
        <List
          onProjectStart={onProjectStart}
          onProjectChange={onProjectChange}
        />
      </Sider>
      <Content>
        <TabsContent
          onClear={clearTabPanesRun}
          onTabDelete={delTabPane}
          onActiveChange={setActiveKey}
          activeKey={activeKey}
          tabList={tabList}
          onWorkDataChange={changeWorkData}
        />
      </Content>
    </Layout>
  );
};

export default TabsPage;
